type EventHandler = (...args: any[]) => void;

/**
 * 中央事件中心
 * 基于发布-订阅模式，用于降低各模块间的耦合度
 */
export default class EventBus {
  private static events: Map<string, EventHandler[]> = new Map();
  /**
   * 注册事件监听器
   * @param event 事件名称
   * @param handler 事件处理函数
   */
  static on(event: string, handler: EventHandler): void {
    if (!this.events.has(event)) {
      this.events.set(event, []);
    }
    this.events.get(event)?.push(handler);
  }

  /**
   * 注册一次性事件监听器，触发后自动移除
   * @param event 事件名称
   * @param handler 事件处理函数
   */
  static once(event: string, handler: EventHandler): void {
    const onceHandler = (...args: any[]) => {
      handler(...args);
      this.off(event, onceHandler);
    };
    this.on(event, onceHandler);
  }

  /**
   * 触发事件
   * @param event 事件名称
   * @param args 传递给事件处理函数的参数
   */
  static emit(event: string, ...args: any[]): void {
    if (this.events.has(event)) {
      const handlers = this.events.get(event) || [];
      handlers.forEach((handler) => {
        handler(...args);
      });
    }
  }

  /**
   * 移除事件监听器
   * @param event 事件名称
   * @param handler 事件处理函数，不传则移除该事件的所有监听器
   */
  static off(event: string, handler?: EventHandler): void {
    if (!handler) {
      // 移除该事件的所有监听器
      this.events.delete(event);
      return;
    }

    // 移除特定的事件监听器
    const handlers = this.events.get(event);
    if (handlers) {
      const index = handlers.indexOf(handler);
      if (index !== -1) {
        handlers.splice(index, 1);
      }
      // 如果没有监听器了，则删除该事件
      if (handlers.length === 0) {
        this.events.delete(event);
      }
    }
  }

  /**
   * 清空所有事件监听器
   */
  static clear(): void {
    this.events.clear();
  }
}
